﻿using System;
using System.Collections.Generic;

namespace BizElements.BusinessLayer
{
    /// <summary>Contains information about weak entity structure, i.e. special fields, and field acces permissions.</summary>
    public class DataObjectDescriptor : IDataObjectDescriptor
    {
        FieldMap fields = new FieldMap();

        #region IDataObjectDescriptor.        

        /// <summary>Gets or sets the map for special entity properties such as ownership fields, audit fields etc. These fields affect various aspects of data, business and UI logic.</summary>
        public FieldMap Fields
        {
            get { return this.fields; }
            set
            {
                if (value == null)
                    throw new ArgumentNullException("value", "Null is not a valid value for Fields property.");

                this.fields = value;
            }
        }

        /// <summary>Gets or sets optional field-level security access permissions. Empty collection if no special field-level access permissions are defined.</summary>
        public IEnumerable<FieldPermissionSet> FieldPermissions { get; set; }

        #endregion

        #region FieldMap - exposed properties.

        /// <summary>Gets or sets the name of optional property that indicates whether the record is active (1) or deactivated/deleted (0).</summary>
        public string StatusPropertyName
        {
            get { return this.Fields.StatusPropertyName; }
            set { this.Fields.StatusPropertyName = value; }
        }

        /// <summary>Gets or sets the name of, typically textual, default property for user interface.</summary>
        public string DefaultPropertyName
        {
            get { return this.Fields.DefaultPropertyName; }
            set { this.Fields.DefaultPropertyName = value; }
        }

        /// <summary>Optional name of default property by which entities are sorted in collections.</summary>
        public string OrderByPropertyName
        {
            get { return this.Fields.OrderByPropertyName; }
            set { this.Fields.OrderByPropertyName = value; }
        }

        /// <summary>Gets or sets the name of optional logging property that contains username of actor that created the entity.</summary>
        public string CreatedByPropertyName
        {
            get { return this.Fields.CreatedByPropertyName; }
            set { this.Fields.CreatedByPropertyName = value; }
        }

        /// <summary>Gets or sets the name of optional date-time property that contains entity creation timestamp.</summary>
        public string CreatedOnPropertyName
        {
            get { return this.Fields.CreatedOnPropertyName; }
            set { this.Fields.CreatedOnPropertyName = value; }
        }

        /// <summary>Gets or sets the name of optional logging property that contains username of actor that was last to update the entity.</summary>
        public string UpdatedByPropertyName
        {
            get { return this.Fields.UpdatedByPropertyName; }
            set { this.Fields.UpdatedByPropertyName = value; }
        }

        /// <summary>Gets or sets the name of optional date-time property that contains last modification timestamp.</summary>
        public string UpdatedOnPropertyName
        {
            get { return this.Fields.UpdatedOnPropertyName; }
            set { this.Fields.UpdatedOnPropertyName = value; }
        }

        /// <summary>Gets or sets the name of optional property that contains a reference to actor/user that owns the entity.</summary>
        public string OwnerIdPropertyName
        {
            get { return this.Fields.OwnerIdPropertyName; }
            set { this.Fields.OwnerIdPropertyName = value; }
        }

        /// <summary>Gets or sets the name of optional property that contains a reference to an organisational unit that owns the entity.</summary>
        public string UnitIdPropertyName
        {
            get { return this.Fields.UnitIdPropertyName; }
            set { this.Fields.UnitIdPropertyName = value; }
        }

        /// <summary>Gets or sets the name of optional property that contains a reference to a team of users that work on entity.</summary>
        public string TeamIdPropertyName
        {
            get { return this.Fields.TeamIdPropertyName; }
            set { this.Fields.TeamIdPropertyName = value; }
        }

        /// <summary>Gets or sets the name of optional property that contains a reference to an organization that owns the entity.</summary>
        public string OrganizationIdPropertyName
        {
            get { return this.Fields.OrganizationIdPropertyName; }
            set { this.Fields.OrganizationIdPropertyName = value; }
        }

        /// <summary>Gets or sets the name of optional property that determines business object subtype, i.e. derived class. 
        /// The values stored in this field are typically used by factory classes to build instances of derived concrete classes.</summary>
        public string SubtypeIdPropertyName
        {
            get { return this.Fields.SubtypeIdPropertyName; }
            set { this.Fields.SubtypeIdPropertyName = value; }
        }

        /// <summary>Gets or sets the names of properties used by optimistic offline concurrency control scheme to check if another user or process has changed the object.
        /// Can be same as <see cref="UpdatedOnPropertyName"/> but it may also be a dedicated timestamp/row-version field or even all of the entity fields.
        /// Empty array or <b>null</b> if optimistic offline locking scheme is not used.</summary>
        public string[] ChangeTrackingPropertyNames
        {
            get { return this.Fields.ChangeTrackingPropertyNames; }
            set { this.Fields.ChangeTrackingPropertyNames = value; }
        }

        #endregion
    }
}